package com.sec.android.app.myfiles.module.local.category.folder;

import android.content.Context;
import android.database.Cursor;
import android.database.CursorIndexOutOfBoundsException;
import android.provider.MediaStore;
import android.text.TextUtils;
import android.view.View;
import android.widget.TextView;

import com.sec.android.app.myfiles.R;
import com.sec.android.app.myfiles.fragment.AbsMyFilesFragment;
import com.sec.android.app.myfiles.info.AppFeatures;
import com.sec.android.app.myfiles.info.FileType;
import com.sec.android.app.myfiles.info.MediaFile;
import com.sec.android.app.myfiles.log.Log;
import com.sec.android.app.myfiles.module.abstraction.FileRecord;
import com.sec.android.app.myfiles.module.local.category.CategoryFileRecord;
import com.sec.android.app.myfiles.module.local.category.CategoryListAdapterImp;
import com.sec.android.app.myfiles.navigation.NavigationInfo;
import com.sec.android.app.myfiles.provider.DbTableInfo;
import com.sec.android.app.myfiles.util.PreferenceUtils;
import com.sec.android.app.myfiles.util.StorageMonitor;
import com.sec.android.app.myfiles.util.UiUtils;
import com.sec.android.app.myfiles.widget.listview.AbsListViewImp;
import com.sec.android.app.myfiles.widget.listview.FileListViewHolder;
import com.sec.android.app.myfiles.widget.listview.ListViewHolder;

import java.util.Locale;

/**
 * Created by jaebae on 2016-09-29.
 */
public class FolderListAdapterImp extends CategoryListAdapterImp {
    private static final String COLUMN_ITEM_COUNT = "_count";
    private static final String COLUMN_TOTAL_SIZE = "total_size";
    private boolean mIsDexColumnListView;

    private long mPrevTotalSize = 0L;


    public FolderListAdapterImp(Context context, NavigationInfo navigationInfo, AbsListViewImp listView, Cursor c, int flags) {
        super(context, navigationInfo, listView, c, flags);
        mTableInfo = FolderDbTableInfo.getInstance();
    }

    @Override
    public String[] getProjection() {
        String[] baseProjection = super.getProjection();
        String defaultSelection = super.getSelection();

        String[] ret = new String[baseProjection.length + 2];
        System.arraycopy(baseProjection, 0, ret, 0, baseProjection.length);

        StringBuilder itemCountQuery = new StringBuilder();
        itemCountQuery.append("(SELECT count(f._id) FROM files AS f")
        .append(" WHERE f.bucket_id = files.bucket_id AND ").append(defaultSelection).append(") AS ").append(COLUMN_ITEM_COUNT);
        ret[ret.length - 2] = itemCountQuery.toString();

        StringBuilder totalSizeQuery = new StringBuilder();
        totalSizeQuery.append("(SELECT sum(f.").append(MediaStore.MediaColumns.SIZE).append(") FROM files AS f")
                .append(" WHERE f.bucket_id = files.bucket_id AND ").append(defaultSelection).append(") AS ").append(COLUMN_TOTAL_SIZE);
        ret[ret.length - 1] = totalSizeQuery.toString();
        return ret;
    }

    @Override
    public String getSelection() {
        String defaultSelection = super.getSelection();

        if (defaultSelection == null || defaultSelection.isEmpty()) {
            defaultSelection = " 1 "; //Always true syntax
        }

        String orderBy = super.getOrderBy();
        orderBy = orderBy.replaceAll("ext", FolderDbTableInfo.EXT_QUERY);

        StringBuilder ret = new StringBuilder();
        ret.append(" _id in (SELECT (SELECT _id")
                .append(" FROM files AS f")
                .append(" WHERE f.bucket_id = bucket_ids.bucket_id").append(" AND ").append(defaultSelection)
                .append(" ORDER BY ").append(orderBy).append(" LIMIT 1")
                .append(") AS _id")
                .append(" FROM (SELECT DISTINCT bucket_id")
                .append(" FROM files WHERE ").append(defaultSelection).append(") AS bucket_ids)");

        return ret.toString();
    }

    @Override
    protected boolean _bindThumbnailView(Context context, ListViewHolder vh, View v, FileRecord record) {
        FileRecord firstChildRecord = FileRecord.createFileRecord(FileRecord.StorageType.Local, ((CategoryFileRecord) record).getFirstItemPath());
        firstChildRecord.setFileType(MediaFile.getFileType(firstChildRecord.getFullPath(), context));
        return super._bindThumbnailView(context, vh, v, firstChildRecord);
    }

    @Override
    protected FileRecord _getFileRecord(Cursor cursor) {
        CategoryFileRecord ret = null;

        final int bucketIdIndex = mTableInfo.getIndex(DbTableInfo.COLUMN_ID.BUCKET_ID);
        final int dateIndex = mTableInfo.getIndex(DbTableInfo.COLUMN_ID.DATE);
        final int pathIndex = mTableInfo.getIndex(DbTableInfo.COLUMN_ID.PATH);

        if (cursor != null) {
            final int itemCountIndex = cursor.getColumnIndex(COLUMN_ITEM_COUNT);
            final int sizeIndex = cursor.getColumnIndex(COLUMN_TOTAL_SIZE);
            try {
                String bucketId = cursor.getString(bucketIdIndex);
                int itemCount = cursor.getInt(itemCountIndex);
                long date = cursor.getLong(dateIndex) * 1000;
                long size = cursor.getLong(sizeIndex);
                String path = cursor.getString(pathIndex);
                String bucketDisplayName = StorageMonitor.getBucketDisplayName(mContext, FileRecord.getPath(path));
                ret = new CategoryFileRecord(0, mCurRecord.getFullPath(), bucketDisplayName, size, date, FileType.FOLDER, 0, itemCount, itemCount);
                ret.setBucketId(bucketId);
                ret.setRealPath(FileRecord.getPath(path));
                ret.setFirstItemPath(path);
            } catch (IllegalStateException e) {
                Log.e(this, "IllegalStateException:" + e.toString());
            } catch (CursorIndexOutOfBoundsException e) {
                Log.e(this, "CursorIndexOutOfBoundsException:" + e.toString());
            }
        }

        return ret;
    }

    @Override
    protected ListViewHolder _createViewHolder(View v) {
        ListViewHolder vh = super._createViewHolder(v);
        vh.addView(FileListViewHolder.SD_CARD_OVERLAY_ICON_STUB, v.findViewById(R.id.sd_card_icon_stub));
        return vh;
    }

    @Override
    protected void _bindView(Context context, ListViewHolder vh, View v, FileRecord record, int position) {
        super._bindView(context, vh, v, record, position);
        _bindSDCardOverlayIcon(vh, v, record);
        mIsDexColumnListView = AppFeatures.isKnoxDesktopMode() && isDetailList(v);
    }

    private void _bindSDCardOverlayIcon(ListViewHolder vh, View v, FileRecord record) {
        View sdcardIcon = vh.getView(FileListViewHolder.SD_CARD_OVERLAY_ICON);
        if (sdcardIcon == null) {
            sdcardIcon = ensureViewFromStub(vh, v, FileListViewHolder.SD_CARD_OVERLAY_ICON_STUB, FileListViewHolder.SD_CARD_OVERLAY_ICON, R.id.sd_card_icon);
        }
        if (sdcardIcon != null) {
            sdcardIcon.setVisibility(StorageMonitor.isSdCardPath(record.getFullPath()) ? View.VISIBLE : View.GONE);
        }
    }

    @Override
    protected void _bindDefaultInfoView(Context context, ListViewHolder vh, FileRecord record) {
        TextView textName = vh.getView(FileListViewHolder.NAME, TextView.class);
        if (textName != null) {
            textName.setText(StorageMonitor.getStorageDisplayName(context, record.getFullPath()));
            textName.setEllipsize(TextUtils.TruncateAt.MIDDLE);
        }

        TextView textDate = vh.getView(FileListViewHolder.DATE, TextView.class);
        if (textDate != null) {
            textDate.setVisibility(View.VISIBLE);
            textDate.setText(UiUtils.makeTimeString(mContext, record.getDate()));
        }

        TextView textSize = vh.getView(FileListViewHolder.SIZE, TextView.class);
        if (textSize != null) {
            textSize.setVisibility(View.VISIBLE);
            String size;
            if (AppFeatures.isTabletUIMode()) {
                boolean showHidden = PreferenceUtils.getShowHiddenFiles(context);
                size = UiUtils.makeItemsString(mContext, record.getItemCount(showHidden));
            } else {
                size = String.format(Locale.getDefault(), "%d", record.getItemCount(false));
            }
            textSize.setText(size);
        }
    }

    @Override
    public boolean _isEnabled(int position) {
        return true;
    }

    @Override
    protected void doFragmentLoadFinished(AbsMyFilesFragment fragment, Cursor data) {
        fragment.onLoadFinished();
    }
}
